#include "game.h"
#include "ui_game.h"
#include <QPushButton>
#include <QButtonGroup>
#include <QRandomGenerator>
#include <QTimer>
#include <QRegularExpression>
#include "widget.h"

game::game(QWidget *parent, QSerialPort *serialPort, Widget *parentWidgetPtr) :
    QWidget(parent),
    ui(new Ui::game),
    count(0),
    gameSerial(serialPort),
    parentWidget(parentWidgetPtr)
{
    ui->setupUi(this);
    gameLayout = new QStackedLayout(ui->gameBackground);

    QWidget *await = new QWidget(this);

    gameLayout->addWidget(await);
    gameLayout->addWidget(ui->gameBody);
    gameLayout->addWidget(ui->finish);
    gameLayout->addWidget(ui->scenario);
    gameLayout->addWidget(ui->shopFinish);

    ui->choiceA->setStyleSheet("#choiceA {"
                               "    color: black;"
                               "}"
                               "#choiceA:checked {"
                               "    color: #FF5733;"  // 选中时为橙色
                               "}");
    ui->choiceB->setStyleSheet("#choiceB {"
                               "    color: black;"
                               "}"
                               "#choiceB:checked {"
                               "    color: #FF5733;"  // 选中时为橙色
                               "}");
    ui->choiceC->setStyleSheet("#choiceC {"
                               "    color: black;"
                               "}"
                               "#choiceC:checked {"
                               "    color: #FF5733;"  // 选中时为橙色
                               "}");


    gameRowCount = this->dbRowCount(0);//获取数据库一共有多少行数据
    QObject::connect(this,&game::sendEmit,this,&game::gameStart);
    QObject::connect(this,&game::sendOver,this,&game::gameOver);
    QObject::connect(this,&game::sceneEmit,this,&game::sceneStart);
    QObject::connect(this,&game::sceneOver,this,&game::sceneFinish);

    // 连接 Widget 的信号到 Game 的槽函数
    connect(parentWidget, &Widget::newDataAvailable, this, &game::onNewData);

    ui->gameBackground->setGraphicsEffect(shadowSet(0));
    ui->button->setGraphicsEffect(shadowSet(0));
    ui->button_2->setGraphicsEffect(shadowSet(0));
    ui->button_3->setGraphicsEffect(shadowSet(0));

    ui->pushButton->setGraphicsEffect(shadowSet(1));
    ui->frame_3->setGraphicsEffect(shadowSet(1));

}

game::~game()
{
    delete ui;
}

QGraphicsDropShadowEffect *game::shadowSet(bool choice)
{
    if(choice == 0)
    {
        //设置阴影特效
        //创建特效对象
        QGraphicsDropShadowEffect *shadow_effect = new QGraphicsDropShadowEffect(this);
        //设置偏移量，x轴，y轴
        shadow_effect->setOffset(2, 2);
        //设置阴影颜色和透明度
        shadow_effect->setColor(QColor(125, 125, 125, 200));
        //设置阴影外射的尺寸
        shadow_effect->setBlurRadius(10);

        return shadow_effect;
    }
    else
    {
        QGraphicsDropShadowEffect* shadow = new QGraphicsDropShadowEffect;

        shadow->setBlurRadius(30);     // 极致模糊
        shadow->setOffset(0, 8);       // 更夸张的偏移
        shadow->setColor(QColor(0, 0, 0, 160)); // 几乎半透明黑

        return shadow;
    }
}

QWidget *game::getGameWidget()
{
    return ui->background;
}

void game::dateInit(QDateTime *nowTime)
{
    QSqlQuery query;
    QString sqlUpdate = QString("update question set choiceA = '%1' where id = 3").arg(nowTime->toString("MM-dd"));
    if(!query.exec(sqlUpdate))
    {
        qDebug() << "update data error" << endl;
    }
    sqlUpdate = QString("update question set choiceB = '%1' where id = 3").arg(nowTime->addDays(1).toString("MM-dd"));
    if(!query.exec(sqlUpdate))
    {
        qDebug() << "update data error" << endl;
    }
    sqlUpdate = QString("update question set choiceC = '%1' where id = 3").arg(nowTime->addDays(-1).toString("MM-dd"));
    if(!query.exec(sqlUpdate))
    {
        qDebug() << "update data error" << endl;
    }
}

//开始和结束训练按钮
void game::on_button_clicked()
{
    //训练开始
    if(ui->button->isChecked())
    {
        ui->button->setText("结束训练");
        ui->choiceA->setChecked(false);
        ui->choiceC->setChecked(false);
        ui->choiceB->setChecked(false);
        gameLayout->setCurrentIndex(1);
        processingEnabled = 1;
        emit this->sendEmit();
    }
    //训练结束
    else
    {
        processingEnabled = 0;
        ui->button->setText("开始训练->");
        gameLayout->setCurrentIndex(0);
        count = 0;
    }
}

void game::on_choiceA_clicked()
{
    ui->choiceB->setChecked(false);
    ui->choiceC->setChecked(false);
}

void game::on_choiceB_clicked()
{
    ui->choiceA->setChecked(false);
    ui->choiceC->setChecked(false);
}

void game::on_choiceC_clicked()
{
    ui->choiceB->setChecked(false);
    ui->choiceA->setChecked(false);
}

//游戏主体
//通过随机数生成获取题目ID，然后根据ID显示题目
void game::gameStart()
{
    gameMode = 1;
    questionID[count] = game::getQuestionId(gameRowCount);
    game::showQuestion(questionID[count]);
    count++;
}

int game::getQuestionId(int rowCount)
{
    int randomInt = 0;
    while(1)
    {
        // 生成 1~rowcount 之间的随机整数
        randomInt = QRandomGenerator::global()->bounded(1,rowCount + 1);
        qDebug() << "random num" << randomInt;
        if(isRepeat(randomInt,0,nullptr,0))//题目不能重复
            break;
    }
    return randomInt;
}

void game::showQuestion(int id)
{
    QSqlQuery query;
    QString sqlCount = QString("SELECT * FROM question WHERE id = %1").arg(id);
    if(!query.exec(sqlCount))
    {
        qDebug() << "query fail" << query.lastError();
    }
    if(query.next())
    {
        QString type = query.value("type").toString();
        QString content = query.value("content").toString();
        QString choice_a = query.value("choiceA").toString();
        QString choice_b = query.value("choiceB").toString();
        QString choice_c = query.value("choiceC").toString();
        QString hint = query.value("hint").toString();
        int grade = query.value("grade").toInt();

        if(type == "single_choice")
        {
            ui->type->setText("选择题");
        }
        else if(type == "true_false")
        {
            ui->type->setText("判断题");
        }

        ui->Question->setText(content);
        ui->choiceA->setText(choice_a);
        ui->choiceB->setText(choice_b);
        ui->choiceC->setText(choice_c);
        if(grade == 1)
        {
            ui->grade->setText("简单");
        }
        else if(grade == 2)
        {
            ui->grade->setText("中等");
        }
        else if(grade == 3)
        {
            ui->grade->setText("困难");
        }

        ui->hint->setText(hint);
    }
}

bool game::isRepeat(int randomCount,uint8_t model,uint8_t (*usdedID)[2],uint8_t picCount)
{
    int i = 0;
    if(model == 0)
    {
        for(i = 0;i < count;i++)
        {
            if(questionID[i] == randomCount)
            {
                return 0;
            }
        }
        return 1;
    }
    else if(model == 1)
    {
        for(i = 0;i < listCount;i++)
        {
            if(ListID[i] == randomCount)
            {
                return 0;
            }
        }
        return 1;
        qDebug() << "retrun 1" << endl;
    }
    else if(model == 2)
    {
        for(i = 0;i < picCount;i++)
        {
            if(usdedID[i][1] == randomCount)
            {
                return 0;
            }
        }
        return 1;
    }

    return 0;
}

int game::dbRowCount(bool model)
{
    int rowCount = 0;
    QSqlQuery query;
    if(model == 0)
    {
        QString sqlCount = QString("SELECT COUNT(*) FROM question");
        if(!query.exec(sqlCount))
        {
            qDebug() << "question query fail" << query.lastError();
        }

        if(query.next())
        {
            rowCount = query.value(0).toInt();
            qDebug() << "question query row:" << rowCount << endl;
        }
    }
    else if(model == 1)
    {
        QString sqlCount = QString("SELECT COUNT(*) FROM shopping_items");
        if(!query.exec(sqlCount))
        {
            qDebug() << "shopping_items query fail" << query.lastError();
        }

        if(query.next())
        {
            rowCount = query.value(0).toInt();
            qDebug() << "shopping_items query row:" << rowCount << endl;
        }
    }

    return rowCount;
}

void game::buttonClick()
{
    ui->button->animateClick();
}

void game::SenceCliked()
{
    ui->button_2->animateClick();
}

void game::dailyClick()
{
    ui->dailyButton->animateClick();
}

void game::meatClick()
{
    ui->meatButton->animateClick();
}

void game::fruiltClick()
{
    ui->fruiltButton->animateClick();
}

void game::packClick()
{
    ui->packButton->animateClick();
}

void game::exitButtonClick()
{
    ui->exitButton->animateClick();
}

//获取购物清单
void game::getShopList(int rowCount)
{
    int randomInt = 0;
    uint8_t i = 0;
    //获取listID
    for(i = 0;i < 4;i++)
    {
        while(1)
        {
            // 生成 1~rowcount 之间的随机整数
            randomInt = QRandomGenerator::global()->bounded(1,rowCount + 1);
            qDebug() << "random num" << randomInt;
            if(isRepeat(randomInt,1,nullptr,0))//题目不能重复
                break;
        }
        ListID[i] = randomInt;
        listCount++;
    }
    //根据listID显示
    QList<QCheckBox *> shopList = {
        ui->toshop1,ui->toshop2,ui->toshop3,ui->toshop4
    };
    for(i = 0;i < 4;i++)
    {
        QSqlQuery query;
        QString sqlCount = QString("SELECT * FROM shopping_items WHERE id = %1").arg(ListID[i]);
        if(!query.exec(sqlCount))
        {
            qDebug() << "query fail" << query.lastError();
        }
        if(query.next())
        {
            QString text = query.value("content").toString();
            shopList[i]->setText(text);
        }
    }
}

void game::clearPic()
{
    QList<QCheckBox *> shopList = {
        ui->pic1,ui->pic2,ui->pic3,ui->pic4
    };
    uint8_t i = 0;
    for(i = 0;i < 4;i++)
    {
        shopList[i]->setStyleSheet("border-image: none;");
        shopList[i]->setChecked(false);
    }
}

void game::clearShopList()
{
    QList<QCheckBox *> shopList = {
        ui->toshop1,ui->toshop2,ui->toshop3,ui->toshop4
    };
    uint8_t i = 0;
    for(i = 0;i < 4;i++)
    {
        shopList[i]->setText("");
        shopList[i]->setChecked(false);
    }
}


void game::showPic(QString zoon)
{
    uint8_t i = 0;
    uint8_t picCount = 0;
    QList<QCheckBox *> pic{
        ui->pic1,ui->pic2,ui->pic3,ui->pic4
    };
    QSqlQuery query;
    QString sqlFind;
    uint8_t showedPicID[4][2] = {{0}};//已经显示了的picID，第一个元素是显示在哪个pic上的ID，第二个是对应数据库的ID
    ui->frame_2->setStyleSheet("#frame_2{border: 10px solid rgb(0,0,255);}");
    for(i = 0;i < 4;i++)
    {
        sqlFind = QString("SELECT * FROM shopping_items WHERE id = %1").arg(ListID[i]);
        if(!query.exec(sqlFind))
        {
            qDebug() << "query fail" << query.lastError();
        }
        if(query.next())
        {
            QString area = query.value("area").toString();
            if(area == zoon)
            {
                QString picPath = query.value("image_path").toString();
                int pathID = query.value("id").toUInt();
                pic[i]->setStyleSheet(QString("border-image: url(%1);").arg(picPath));
                showedPicID[i][0] = i + 1;//第一个元素等于显示在哪个pic上的id
                showedPicID[i][1] = pathID;
                picCount++;
            }
            else
            {
                sqlFind = QString("SELECT * FROM shopping_items WHERE area = '%1'").arg(zoon);
                if(!query.exec(sqlFind))
                {
                    qDebug() << "query fail" << query.lastError();
                }
                while(query.next())
                {
                    QString picPath = query.value("image_path").toString();
                    int pathID = query.value("id").toUInt();
                    if(isRepeat(pathID,2,showedPicID,picCount))
                    {
                        pic[i]->setStyleSheet(QString("border-image: url(%1);").arg(picPath));
                        showedPicID[i][0] = i + 1;//第一个元素等于显示在哪个pic上的id
                        showedPicID[i][1] = pathID;
                        picCount++;
                        break;
                    }
                }
            }
        }
    }

}

QString game::extractBorderImage(const QString &styleSheet)
{
    // 查找 "border-image: url(" 的起始位置
        QString key = "border-image: url(";
        int startPos = styleSheet.indexOf(key, Qt::CaseInsensitive);
        if (startPos == -1) {
            return QString(); // 没有找到 border-image
        }

        // 计算 URL 起始位置（跳过 "border-image: url("）
        startPos += key.length();

        // 查找右括号 ")"
        int endPos = styleSheet.indexOf(')', startPos);
        if (endPos == -1) {
            return QString(); // 没有找到右括号
        }

        // 提取括号中的内容（即 URL）
        QString urlContent = styleSheet.mid(startPos, endPos - startPos);

        // 去除 URL 前后的空白字符
        return urlContent.trimmed();
}

void game::checkPicClick(QCheckBox *pic)
{
    qDebug() << pic->styleSheet() << endl;
    QString borderImage = extractBorderImage(pic->styleSheet());
    if(!borderImage.isEmpty())
    {
        uint8_t i = 0;
        qDebug() << "Border image URL:" << borderImage;
        QList<QCheckBox *> shopList = {
            ui->toshop1,ui->toshop2,ui->toshop3,ui->toshop4
        };
        for(i = 0;i < 4;i++)
        {
            QSqlQuery query;
            QString sqlCount = QString("SELECT * FROM shopping_items WHERE id = %1").arg(ListID[i]);
            if(!query.exec(sqlCount))
            {
                qDebug() << "query fail" << query.lastError();
            }
            if(query.next())
            {
                QString picPath = query.value("image_path").toString();
                if(borderImage == picPath)
                {
                    shopList[i]->animateClick();
                }
            }
        }
    }
}


void game::on_pushButton_clicked()
{
    QSqlQuery query;
    QString sqlCount = QString("SELECT * FROM question WHERE id = %1").arg(questionID[count - 1]);
    if(!query.exec(sqlCount))
    {
        qDebug() << "query fail" << query.lastError();
    }
    if(query.next())
    {
        QString answer = query.value("answer").toString();
        if(answer == "A")
        {
            if(ui->choiceA->isChecked())
            {
                ui->hint->setText("恭喜您，答对啦!");
                gameSerial->write("right");
                answeredID[count - 1] = 1;
            }
            else
            {
                ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                gameSerial->write("false");
                answeredID[count - 1] = 2;
            }
        }
        else if(answer == "B")
        {
            if(ui->choiceB->isChecked())
            {
                ui->hint->setText("恭喜您，答对啦!");
                gameSerial->write("right");
                answeredID[count - 1] = 1;
            }
            else
            {
                ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                gameSerial->write("false");
                answeredID[count - 1] = 2;
            }
        }
        else if(answer == "C")
        {
            if(ui->choiceC->isChecked())
            {
                ui->hint->setText("恭喜您，答对啦!");
                gameSerial->write("right");
                answeredID[count - 1] = 1;
            }
            else
            {
                ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                gameSerial->write("false");
                answeredID[count - 1] = 2;
            }
        }
        if(count == 4)//后续要把rowcount改为4，一次游戏4道题
        {
            QTimer::singleShot(1500, this, [this](){
                ui->choiceA->setChecked(false);
                ui->choiceB->setChecked(false);
                ui->choiceC->setChecked(false);
                ui->hint->setText("");
                emit this->sendOver();
            });

        }
        else
        {
            // 延迟 2 秒后执行某项操作
            QTimer::singleShot(2000, this, [this]() {
                ui->choiceA->setChecked(false);
                ui->choiceB->setChecked(false);
                ui->choiceC->setChecked(false);
                ui->hint->setText("");
                emit this->sendEmit();
            });
        }

    }
}

void game::gameOver()
{
    int correctCount = 0;
    int i = 0;
    gameMode = 0;
    for(i = 0;i < count;i++)
    {
        if(answeredID[i] == 1)
        {
            correctCount++;
        }
    }
    ui->accuracy->setText(QString("%1%").arg(correctCount * 10 * 2.5));
    if(correctCount <= 1)
    {
        gameSerial->write("answer1");
    }
    else if(correctCount >= 2 && correctCount <= 3)
    {
        gameSerial->write("answer2");
    }
    else if(correctCount == 4)
    {
        gameSerial->write("answer3");
    }
    gameLayout->setCurrentIndex(2);
}

void game::onNewData()
{
    if(processingEnabled)
    {
        // 从 Widget 的缓冲区获取数据
        QByteArray data = parentWidget->serialBuffer;
        qDebug() << gameMode << endl;
        if(gameMode == 2)
        {
            QString choice = QString::fromUtf8(data);
            qDebug() << choice << endl;
            if(choice == "choiceA")
            {
                ui->pic1->animateClick();
            }
            if(choice == "choiceB")
            {
                ui->pic2->animateClick();
            }
            if(choice == "choiceC")
            {
                ui->pic3->animateClick();
            }
            if(choice == "choiceD")
            {
                ui->pic4->animateClick();
            }
        }
        else if(gameMode == 1)
        {
            QString choice = QString::fromUtf8(data);
            qDebug() << choice << endl;
            QSqlQuery query;
            QString sqlCount = QString("SELECT * FROM question WHERE id = %1").arg(questionID[count - 1]);
            if(!query.exec(sqlCount))
            {
                qDebug() << "query fail" << query.lastError();
            }
            if(query.next())
            {
                QString answer = query.value("answer").toString();
                if(answer == "A")
                {
                    if(choice == "choiceA")
                    {
                        ui->hint->setText("恭喜您，答对啦!");
                        gameSerial->write("right");
                        answeredID[count - 1] = 1;
                    }
                    else
                    {
                        ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                        gameSerial->write("false");
                        answeredID[count - 1] = 2;
                    }
                }
                else if(answer == "B")
                {
                    if(choice == "choiceB")
                    {
                        ui->hint->setText("恭喜您，答对啦!");
                        gameSerial->write("right");
                        answeredID[count - 1] = 1;
                    }
                    else
                    {
                        ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                        gameSerial->write("false");
                        answeredID[count - 1] = 2;
                    }
                }
                else if(answer == "C")
                {
                    if(choice == "choiceC")
                    {
                        ui->hint->setText("恭喜您，答对啦!");
                        gameSerial->write("right");
                        answeredID[count - 1] = 1;
                    }
                    else
                    {
                        ui->hint->setText(QString("很遗憾，正确答案是: %1").arg(answer));
                        gameSerial->write("false");
                        answeredID[count - 1] = 2;
                    }
                }

                if(count == 4)//后续要把rowcount改为10，一次游戏十道题
                {
                    QTimer::singleShot(2000, this, [this](){
                        ui->choiceA->setChecked(false);
                        ui->choiceB->setChecked(false);
                        ui->choiceC->setChecked(false);
                        ui->hint->setText("");
                        emit this->sendOver();
                    });
                }
                else
                {
                    // 延迟 2 秒后执行某项操作
                    QTimer::singleShot(2000, this, [this]() {
                        ui->choiceA->setChecked(false);
                        ui->choiceB->setChecked(false);
                        ui->choiceC->setChecked(false);
                        ui->hint->setText("");
                        emit this->sendEmit();
                    });
                }
            }
        }

        // 清空已处理的数据（根据需求选择是否清空）
        parentWidget->serialBuffer.clear();
    }
}


void game::on_button_2_clicked()
{
    //开始情景模拟
    if(ui->button_2->isChecked())
    {
        gameMode = 2;
        processingEnabled = 1;
        ui->button_2->setText("结束情景");
        gameLayout->setCurrentIndex(3);
        //先发语音
        gameSerial->write("entry");
        //延时两秒进入
        QTimer::singleShot(2000, this, [this](){
            emit this->sceneEmit();
        });
    }
    //结束情景模拟
    else
    {
        ui->button_2->setText("情景模拟");
        ui->scenario->setStyleSheet("#scenario{"
                                    "border-image: url(:/pics/entry.jpg);"
                                    "}");
        ui->frame_2->setStyleSheet("");
        listCount = 0;
        shoppedCount = 0;
        memset(selectID,0,sizeof(selectID));
        memset(ListID,0,sizeof(ListID));
        this->clearPic();
        this->clearShopList();
        gameLayout->setCurrentIndex(0);
    }
}

void game::on_dailyButton_clicked()
{
    ui->scenario->setStyleSheet("#scenario{"
                                "border-image: url(:/pics/dailyArea.jpg);"
                                "}");
    this->clearPic();
    showPic(QString("生活区"));
    gameSerial->write("daily");
}

void game::on_meatButton_clicked()
{
    ui->scenario->setStyleSheet("#scenario{"
                                "border-image: url(:/pics/meat.jpg);"
                                "}");
    this->clearPic();
    showPic(QString("肉类区"));
    gameSerial->write("meat");
}

void game::on_fruiltButton_clicked()
{
    ui->scenario->setStyleSheet("#scenario{"
                                "border-image: url(:/pics/fruilt.jpg);"
                                "}");
    this->clearPic();
    showPic(QString("蔬果区"));
    gameSerial->write("fruilt");
}

void game::on_packButton_clicked()
{
    ui->scenario->setStyleSheet("#scenario{"
                                "border-image: url(:/pics/pack.jpg);"
                                "}");
    this->clearPic();
    showPic(QString("包装食品区"));
    gameSerial->write("pack");
}

void game::sceneStart()
{
    int tableRowCount = this->dbRowCount(1);
    this->getShopList(tableRowCount);
}

void game::sceneFinish()
{
    uint8_t i = 0;
    gameMode = 0;
    processingEnabled = 0;
    gameSerial->write("finish");
    gameLayout->setCurrentIndex(4);
    ui->ratio->setText(QString("%1/4").arg(shoppedCount));
    if(shoppedCount == 4)
    {
        ui->encourage->setText("您已选择购物清单上所有商品");
    }
    else
    {
        QString lost = "您未选择到:";
        for(i = 0;i < 4;i++)
        {
            if(selectID[i] != ListID[i])
            {
                QSqlQuery query;
                QString sqlCount = QString("SELECT * FROM shopping_items WHERE id = %1").arg(ListID[i]);
                if(!query.exec(sqlCount))
                {
                    qDebug() << "query fail" << query.lastError();
                }
                if(query.next())
                {
                    QString str = query.value("content").toString();
                    lost.append(str).append(" ");
                }
            }
        }
        ui->encourage->setText(lost);
    }
}

void game::on_exitButton_clicked()
{
    ui->scenario->setStyleSheet("#scenario{"
                                "border-image: url(:/pics/entry.jpg);"
                                "}");
    this->clearPic();
    ui->frame_2->setStyleSheet("");
    uint8_t i = 0;
    QList<QCheckBox *> shopList = {
        ui->toshop1,ui->toshop2,ui->toshop3,ui->toshop4
    };
    for(i = 0;i < 4;i++)
    {
        if(shopList[i]->checkState())
        {
            selectID[i] = ListID[i];
            shoppedCount++;
        }
    }
    emit this->sceneOver();
}

void game::on_pic1_clicked()
{
    if(ui->pic1->isChecked())
    {
        this->checkPicClick(ui->pic1);
    }
}


void game::on_pic2_clicked()
{
    if(ui->pic2->isChecked())
    {
        this->checkPicClick(ui->pic2);
    }
}

void game::on_pic3_clicked()
{
    if(ui->pic3->isChecked())
    {
        this->checkPicClick(ui->pic3);
    }
}

void game::on_pic4_clicked()
{
    if(ui->pic4->isChecked())
    {
        this->checkPicClick(ui->pic4);
    }
}



void game::on_button_3_clicked()
{
    parentWidget->m_stackedLayout->setCurrentIndex(0);
}
